package block

import (
	"crypto/sha256"
	"encoding/hex"
	"fmt"
	"strconv"
	"strings"
	"time"
)

type Block struct {
	PreHash string
	HashCode string
	TimeStamp string
	Diff int
	Data string
	Index int
	Nonce int
}

func GenerateFirstBlock(data string) Block {
	var firstBlock Block
	firstBlock.PreHash = "0"
	firstBlock.TimeStamp = time.Now().String()
	firstBlock.Diff = 4
	firstBlock.Data = data
	firstBlock.Index = 1
	firstBlock.Nonce = 0
	firstBlock.HashCode = GenerationHashValue(firstBlock)

	return firstBlock
}

func GenerationHashValue(block Block) string{
	var hashdata = strconv.Itoa(block.Index) + strconv.Itoa(block.Nonce) + strconv.Itoa(block.Diff) + block.TimeStamp

	var sha = sha256.New()
	sha.Write([]byte(hashdata))
	hashed := sha.Sum(nil)

	return hex.EncodeToString(hashed)
}

func GenerateNextBlock(data string, oldBlock Block) Block{
	var newBlock Block
	newBlock.PreHash = oldBlock.HashCode
	newBlock.TimeStamp = time.Now().String()
	newBlock.Diff = 4
	newBlock.Data = data
	newBlock.Index = 2
	newBlock.Nonce = 0
	newBlock.HashCode = Pow(newBlock.Diff, &newBlock)
	
	return newBlock
}

func Pow(diff int, block *Block) string{
	for {
		hash := GenerationHashValue(*block)
		fmt.Println(hash)
		if strings.HasPrefix(hash, strings.Repeat("0", diff)) {
			fmt.Println("挖矿成功")
			return hash
		}else{
			block.Nonce++
		}
	}
}